#include "DXDraw2D.h"
#include "GpMacro.h"

int DrawLine(int iX1,int iY1,int iX2,int iY2,DWORD dwColor,UINT* ucBuffer,int iPitch)
{
	int dx,             // difference in x's
		dy,             // difference in y's
		dx2,            // dx,dy * 2
		dy2, 
		x_inc,          // amount in pixel space to move during drawing
		y_inc,          // amount in pixel space to move during drawing
		error,          // the discriminant i.e. error i.e. decision variable
		index;          // used for looping

	int lpitch_2 = iPitch >> 2; // UINT strided lpitch

	// pre-compute first pixel address in video buffer based on 16bit data
	UINT* ucBuffer2 = (UINT*)ucBuffer + iX1 + iY1*lpitch_2;

	// compute horizontal and vertical deltas
	dx = iX2-iX1;
	dy = iY2-iY1;

	// test which direction the line is going in i.e. slope angle
	if(dx>=0)
	{
		x_inc = 1;
	} // end if line is moving right
	else
	{
		x_inc = -1;
		dx    = -dx;  // need absolute value
	} // end else moving left

	// test y component of slope
	if(dy>=0)
	{
		y_inc = lpitch_2;
	} // end if line is moving down
	else
	{
		y_inc = -lpitch_2;
		dy    = -dy;  // need absolute value
	} // end else moving up

	// compute (dx,dy) * 2
	dx2 = dx << 1;
	dy2 = dy << 1;

	// now based on which delta is greater we can draw the line
	if(dx > dy)
	{
		// initialize error term
		error = dy2 - dx; 

		// draw the line
		for(index=0; index <= dx; index++)
		{
			// set the pixel
			*ucBuffer2 = (UINT)dwColor;

			// test if error has overflowed
			if (error >= 0) 
			{
				error-=dx2;

				// move to next line
				ucBuffer2+=y_inc;

			} // end if error overflowed

			// adjust the error term
			error+=dy2;

			// move to the next pixel
			ucBuffer2+=x_inc;

		} // end for

	} // end if |slope| <= 1
	else
	{
		// initialize error term
		error = dx2 - dy; 

		// draw the line
		for (index=0; index <= dy; index++)
		{
			// set the pixel
			*ucBuffer2 = (UINT)dwColor;

			// test if error overflowed
			if (error >= 0)
			{
				error-=dy2;

				// move to next line
				ucBuffer2+=x_inc;

			} // end if error overflowed

			// adjust the error term
			error+=dx2;

			// move to the next pixel
			ucBuffer2+=y_inc;

		} // end for

	} // end else |slope| > 1

	// return success
	return 1;
}

int DrawRectangle(int iX1,int iY1,int iX2,int iY2,DWORD dwColor,LPDIRECTDRAWSURFACE7 lpdds)
{
	DDBLTFX ddbltfx; // this contains the DDBLTFX structure
	RECT fill_area;  // this contains the destination rectangle

	// clear out the structure and set the size field 
	DDRAW_INIT_STRUCT(ddbltfx);

	// set the dwfillcolor field to the desired color
	ddbltfx.dwFillColor = dwColor; 

	// fill in the destination rectangle data (your data)
	fill_area.top    = iX1;
	fill_area.left   = iY1;
	fill_area.bottom = iX2;
	fill_area.right  = iY2;

	// ready to blt to surface, in this case blt to primary
	lpdds->Blt(&fill_area, // ptr to dest rectangle
		NULL,       // ptr to source surface, NA            
		NULL,       // ptr to source rectangle, NA
		DDBLT_COLORFILL | DDBLT_WAIT,   // fill and wait                   
		&ddbltfx);  // ptr to DDBLTFX structure

	return 1;
}